<template>
    <div ref="domBox" :style="{ width, height }">
        <div ref="domRef" :style="{ width, height }" />
    </div>
</template>

<script lang="ts" setup>
import { ResizeObserver } from '@juggle/resize-observer'

const props = withDefaults(
    defineProps<{
        width?: string
        height?: string
        loading?: boolean
        options: any
    }>(),
    {
        width: '100%',
        height: '100%',
        loading: false,
    },
)

watch(
    () => props.loading,
    () => {
        if (chartObj) {
            if (props.loading) {
                chartObj.showLoading({
                    text: '',
                    color: '#15FFAB',
                    textColor: '#fff',
                    maskColor: 'rgba(0, 0, 0, 1)',
                    zlevel: 0,
                    lineWidth: 2,
                })
            }
            if (!props.loading) {
                chartObj.hideLoading()
            }
        }
    },
)

const domRef = ref(null)
const domBox = ref(null)
let chartObj: any = null
let observer: null | ResizeObserver = null // dom 监听
let observerCallback: any = null
let isInResizeObserver = false // 第一次的resize不需要

const drawOption = () => {
    chartObj && props.options && chartObj.setOption(props.options, true)
}

onMounted(() => {
    if (!chartObj && domRef.value) {
        chartObj = window.rawWindow.echarts.init(domRef.value)
    }
    if (!chartObj) {
        return
    }
    if (props.loading) {
        chartObj.showLoading({
            text: '',
            color: '#15FFAB',
            textColor: '#fff',
            maskColor: 'rgba(0, 0, 0, 1)',
            zlevel: 0,
            lineWidth: 2,
        })
    }
    if (!props.loading) {
        chartObj.hideLoading()
    }
    if (props.options) {
        drawOption()
    }

    observerCallback = () => {
        if (isInResizeObserver) {
            if (chartObj) {
                chartObj.resize()
            }
            return
        }
        isInResizeObserver = true
    }
    observer = new window.ResizeObserver(observerCallback)

    nextTick(() => {
        domBox.value && observer?.observe(domBox.value)
    })

    setTimeout(() => {
        chartObj && chartObj.resize()
    }, 1000)
})

onUnmounted(() => {
    if (chartObj) {
        chartObj.dispose()
        chartObj = null
    }
    if (observer && domRef.value) {
        observer.disconnect()
        observer.unobserve(domRef.value)
    }
})

watch(
    () => props.options,
    () => {
        drawOption()
    },
)
</script>
